
package replica;
import generalResourceLalla.Costanti;
import java.io.IOException;
import java.util.Collection;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.xml.parsers.ParserConfigurationException;
import org.xml.sax.SAXException;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.DocumentBuilder;
import org.w3c.dom.Document;
import org.w3c.dom.NodeList;
import org.w3c.dom.Element;
import java.io.File;
import java.io.FileNotFoundException;
import java.util.LinkedList;
import java.util.List;
import java.util.StringTokenizer;
import replica.communication.JMSAdapterFrontEnd;
import replica.transaction.FrontEnd;


/**
 *
 * @author andrea
 */
public class NetworkParser
{
    private String xmlFile;
    List<ReplicaDescriptor> replicaDescriptors=null;
    
    /*
    private LinkedList<ReplicaDescriptor> replicaList=null;
     private LinkedList<FrontEnd> frontEndList=null;
     * 
     */
   
    
    public NetworkParser(String xmlFile) throws IOException, ParserConfigurationException, SAXException
    {
        this.xmlFile=xmlFile;
        parse();
    }
    
    /**
    public LinkedList<ReplicaDescriptor> getReplicaDescriptorList()
    {
        if (this.replicaList==null)
            throw new NullPointerException("replicaList is "+replicaList+
                    ".Maybe you forgot to call NetworkParser.parse() first");
        return this.replicaList;
    }
      
    
    public LinkedList<FrontEnd> getFrontEndList()
    {
        if (this.frontEndList==null)
            throw new NullPointerException("frontEndList is "+frontEndList+
                    ".Maybe you forgot to call NetworkParser.parse() first");
        
        return this.frontEndList;
    }
    */
    
    private void parse() 
        throws ParserConfigurationException, SAXException, IOException
    { 
        try{
            File fXmlFile = new File(this.xmlFile);
            DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
            DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
            Document doc = (Document) dBuilder.parse(fXmlFile);

            doc.getDocumentElement().normalize();
            
            this.replicaDescriptors=new LinkedList<ReplicaDescriptor>();

            NodeList nList = doc.getElementsByTagName("node");
            for (int i = 0; i < nList.getLength(); i++)
            { 
                org.w3c.dom.Node nNode = nList.item(i);
                this.replicaDescriptors.add(parseReplica((Element) nNode));
                
            }
        }catch(FileNotFoundException fnfe)
        {
            System.err.println("File "+this.xmlFile+" not found.");
            fnfe.printStackTrace();
            System.exit(-2436);
        }
    }
    
    public List<Long> getNodeIds()
    {
        List<Long> nodeIds=new LinkedList<Long>();
        for (ReplicaDescriptor r:this.replicaDescriptors)
            nodeIds.add(r.getNodeId());
        return nodeIds;
    }
    
    public List<ReplicaDescriptor> getReplicaDescriptors()
    {
        return this.replicaDescriptors;
    }
    
    /*
    public void parseVecchio() 
        throws ParserConfigurationException, SAXException, IOException
    { 
        File fXmlFile = new File(this.xmlFile);
	DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
	DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
	Document doc = (Document) dBuilder.parse(fXmlFile);
        
	doc.getDocumentElement().normalize();
        //Read replicaDescriptors
        this.replicaList=new LinkedList<ReplicaDescriptor>();
        this.frontEndList=new LinkedList<FrontEnd>();
        NodeList nList = doc.getElementsByTagName("node");
        for (int i = 0; i < nList.getLength(); i++)
        { 
            org.w3c.dom.Node nNode = nList.item(i);
            ReplicaDescriptor netReplica=parseReplica((Element) nNode);
            replicaList.add(netReplica );
            FrontEnd netFrontEnd=parseFrontEnd((Element) nNode);
            frontEndList.add(netFrontEnd );
        }
    }
    */
    
    private long getNodeId(Element e)
    {
        return Long.parseLong(e.getAttribute("id"));
    }
    
    private int getQueueCapacity(Element e)
    {
        int returnValue=-1;
        try{
            returnValue=Integer.parseInt(e.getAttribute("capacity"));
        }catch(NumberFormatException nfe)
        {
            System.err.println("Error in "+e);
            nfe.printStackTrace();
            System.exit(-384763);
        }
        return returnValue;
    }
    

    private ReplicaDescriptor parseReplica(Element e) 
    {
        try{
            int id = Integer.parseInt(e.getAttribute("id"));
            String address=e.getAttribute("address");
            int numberOfCpus=
                    Integer.parseInt(e.getAttribute("numberOfCpus"));
            String memory=e.getAttribute("memory");
            int fileserverPort=Integer.parseInt(
                    e.getAttribute("fileserverPort") );
            
            String mEvents=e.getAttribute("maskedEvents");
            LinkedList<String> maskedEvents=new LinkedList<String>();
            StringTokenizer s = new StringTokenizer(mEvents, ",");
                while(s.hasMoreTokens())
                {
                    String me = s.nextToken();
                    maskedEvents.add(me);
                }
            
            String saturationPolicy=e.getAttribute("saturationPolicy");
            
            String onTaskTxFailurePolicy=e.getAttribute("onTaskTxFailurePolicy");

            NodeList nList = e.getElementsByTagName("taskQueue");
            org.w3c.dom.Node nNode = nList.item(0);
            Element taskQueue=(Element) nNode;
            int taskListenPort=Integer.parseInt(
                    taskQueue.getAttribute("listenPort"));
            int taskQueueCapacity=Integer.parseInt(
                    taskQueue.getAttribute("capacity"));
             /* int taskQueueCapacityLimit=Integer.parseInt(
                    taskQueue.getAttribute("capacityLimit"));*/
            String taskQueueCapacityLimit=taskQueue.getAttribute("capacityLimit");
            //tolgo il simbolo % dalla stringa
            taskQueueCapacityLimit=taskQueueCapacityLimit.replaceFirst("%","");
            System.out.println("Capacity limit is: "+taskQueueCapacityLimit);
            int capacityLimit=Integer.parseInt(taskQueueCapacityLimit);
            String enqueueTaskCode=taskQueue.getAttribute("enqueueCode");
            String dequeueTaskCode=taskQueue.getAttribute("dequeueCode");


            nList = e.getElementsByTagName("eventQueue");
            nNode = nList.item(0);
            Element eventQueue=(Element) nNode;
            int eventListenPort=Integer.parseInt(
                    eventQueue.getAttribute("listenPort"));
            int eventQueueCapacity=Integer.parseInt(
                    eventQueue.getAttribute("capacity"));
            String enqueueEventCode=eventQueue.getAttribute("enqueueCode");
            String dequeueEventCode=eventQueue.getAttribute("dequeueCode");
            
            int illnessWeight;
            

            return new ReplicaDescriptor(id, taskQueueCapacity);
        
         
        }catch(Exception ex)
        {
            System.out.println(ex);
            System.exit(-83773); 
            return null;
        }
    }
    

   
}
